#include "IBUS.h"

uint16_t ibusVal[8];
uint16_t s_IB[32];
uint8_t i_IBUS = 0;
bool ibusNew = 0;

void INIT_IBUS(void)
{//初始化IBUS参数
  Serial.begin(115200);
}

void IBUS_DECODE(uint8_t in)
{//IBUS解码程序
  static uint16_t checksum;//校验
  switch (i_IBUS)
  {
  case 0://判断帧头
    if (in == 0x20)
    {//如果是0x20
      for (uint8_t j = 0; j < 32; j ++)
      {//清空缓存区
        s_IB[j] = 0;
      }
      checksum = in;//校验值初值赋值为输入值
      s_IB[i_IBUS] = in;//将输入数据纳入缓存
      i_IBUS ++;//索引上涨
    }
    break;

  case 1://特征字2
    if (in == 0x40)
    {//如果是0x40，输入数据纳入缓存
      s_IB[i_IBUS] = in;
      checksum += in;//校验值相加
      i_IBUS ++;
    }
    else
    {//否则跳出到帧头判断
      i_IBUS = 0;
    }
    break;

  default://默认状态接收数据
    s_IB[i_IBUS] = in;
    checksum += in;//校验值相加
    i_IBUS ++;
    break;

  case 30://第30byte判断校验值低位
    checksum ^= 0xFFFF;//校验值与0xFFFF异或
    if (in == (checksum & 0xFF))
    {//取低位，如果相符，进入下一步
      s_IB[i_IBUS] = in;
      i_IBUS ++;
    }
    else
    {//如果不符
      i_IBUS = 0;//跳出至帧头判断
    }
    break;

  case 31://第31byte判断校验值高位
    if (in == (checksum >> 8))
    {//取低位，如果相符，解算前8通道数据
      s_IB[i_IBUS] = in;
      for (uint8_t j = 0; j <= 7; j ++)
      {
        ibusVal[j] = s_IB[j * 2 + 2] | (s_IB[j * 2 + 3] << 8);
      }
      ibusNew = 1;//新数据标志位更新
    }
    i_IBUS = 0;//进入帧头判断
    break;
  }
}

uint16_t IBUS_VAL(uint8_t channel)
{
  return ibusVal[channel];
}

bool IBUS_UPDATED(void)
{
  bool old = ibusNew;
  ibusNew = 0;
  return old;
}
